/*************************************************************
 * @file       usart.c
 * @brief      串口配置和中断服务程序
 *
 *
 * @version    Verison	0.0
 * @author     xieyoub
 * @data       2017/06/08
 *************************************************************/

#include "usart.h"
#include "string.h"
#include "lpc17xx_pinsel.h"
#include "GUI.h"
#include "dma.h"
#include "tones.h"

#include "GUI_Message.h"

#include "macService.h"

#include "ipc.h"


#include "gpio.h"
#include "key.h"
#include "nvic.h"

#include "lpc17xx_wdt.h"

#include "flash.h"

/** @addtogroup  串口配置
  * 
  *  @{
  */

uint16_t GetCrc(uint8_t *p, uint16_t Length);
void SetResultCrc(uint8_t *p, char CmdType, char Result, char ErrType);

/**< 数据接收缓冲区     */
UART_BUF_R	uart0RxBuf;
UART_BUF_R	uart1RxBuf;
UART_BUF_R	uart2RxBuf;
UART_BUF_R	uart3RxBuf;


void wwdg_init(void)
{
    LPC_SC->PCLKSEL0 |= (3<<0);
    LPC_WDT->WDCLKSEL &= ~(3<<0);
    LPC_WDT->WDCLKSEL |= (1<<0);
    LPC_WDT->WDCLKSEL |= (1<<31);
    LPC_WDT->WDTC = 0xffff;
    LPC_WDT->WDMOD |= (1<<0)|(1<<1);
}
static uint32_t BoatSearchResult[5];


 /**< 串口1数据 缓冲    */
UART1Data uart1Data;

 /**< 串口3数据 缓冲    */
UART3Data uart3Data;

__asm void jump(uint32_t addr)
{
   LDR SP, [R0]		           ;Load new stack pointer address
   LDR PC, [R0, #4]	         ;Load new program counter address
}

/***********************中断服务*********************************/

/**	@brief 		串口0中断服务函数
  * 
  * @note
  */
void UART0_IRQHandler(void)
{
		uint32_t intsrc, tmp, tmp1;
    uint8_t data[5];
		/* Determine the interrupt source */
		intsrc = UART_GetIntId(LPC_UART0);
		tmp = intsrc & UART_IIR_INTID_MASK; //IIR[3:0]
	
	/**< 字符超时     */
	if(tmp == UART_IIR_INTID_CTI){
		UART_IntReceive(LPC_UART0);
		//AudioPlayCnt(AUDIO_TYPE_KEY_NORMAL,AUDIO_PLAY_TIMES_KEY_NORMAL);
		//printf("uart1\n");
		//UART_Send(LPC_UART0,uart0RxBuf.rx,uart0RxBuf.pIndex,BLOCKING);
//		TonesWriteToFlash(uart0RxBuf.rx,tonesFileAdd,uart0RxBuf.pIndex);
//		tonesFileAdd += uart0RxBuf.pIndex;
    tmp = GetCrc(uart0RxBuf.rx, uart0RxBuf.pIndex - 2);
		if(tmp == (uart0RxBuf.rx[uart0RxBuf.pIndex-2]<<8 | uart0RxBuf.rx[uart0RxBuf.pIndex-1]))
    {
      if(uart0RxBuf.rx[0] == 0x55)
      {
        SetResultCrc(data, 0,0x5a, 0);
        Uart0_SendBytes(3, data);
      }
      else if(uart0RxBuf.rx[0] == 0x56)
      {
        SetResultCrc(data, 0,0x56, 0);
        Uart0_SendBytes(3, data);
      }
      else if(uart0RxBuf.rx[0] == 0x16)
      {
        SetResultCrc(data, 0,0x16, 0);
        Uart0_SendBytes(3, data);
      }
      else if(uart0RxBuf.rx[0] == 0x0d)
      {
        SetResultCrc(data, 0, 'S', 0);
        Uart0_SendBytes(3, data);
        
        //FPGAResetEnable();
//        for(int i=1000;i>0;i--){
//          for(int i=100;i>0;i--);
//        }
        CLKPWR_ConfigPPWR (CLKPWR_PCONP_PCUART0, DISABLE);
        __disable_irq();
        //NVIC_SystemReset();
        //看门狗复位
        // Initialize WDT, IRC OSC, interrupt mode, timeout = 100us 
        WDT_Init(WDT_CLKSRC_IRC, WDT_MODE_RESET);
        WDT_Start(100);
//        __disable_irq();
//        jump(0);
      }
      else if(uart0RxBuf.rx[0] == 'E')
      {
        SetResultCrc(data, 0, 'S', 0);
        Uart0_SendBytes(3, data);
        __disable_irq();
        SPI_Flash_Erase_Sector(FLASH_ADDRESS_SYS_CONFIG / 0x1000);
        SPI_Flash_Erase_Sector(FLASH_ADDRESS_CONTACT / 0x1000);
        SPI_Flash_Erase_Sector(FLASH_ADDRESS_CALL_LOG / 0x1000);
        SPI_Flash_Erase_Sector(FLASH_ADDRESS_FAVORITE / 0x1000);
        SPI_Flash_Erase_Sector(FLASH_ADDRESS_COOKIES / 0x1000);
        WDT_Init(WDT_CLKSRC_IRC, WDT_MODE_RESET);
        WDT_Start(100);
      }
    }
		memset(&uart0RxBuf,0,sizeof(UART_BUF_R));
	}

	/**< FIFO数据大于触发点     */
	if(tmp == UART_IIR_INTID_RDA)
	{
		UART_IntReceive(LPC_UART0);
		//UART_SendByte(LPC_UART0,0x04);
	}
		
}

/**	@brief 		串口1中断服务函数
  * 
  * 串口 1 rx 接收两个字节  格式为 0xad + info(1字节)
  * @note
  */
void UART1_IRQHandler(void)
{
#ifdef USE_CRITICAL_WHEN_POST    
    
#if OS_CRITICAL_METHOD == 3u	 
	 OS_CPU_SR cpu_sr  = 0u;
#endif	
	
	OS_ENTER_CRITICAL();
#endif 	
    
    uint32_t intsrc, tmp, tmp1;

   
	/* Determine the interrupt source */
	intsrc = UART_GetIntId((LPC_UART_TypeDef*)LPC_UART1);
	tmp = intsrc & UART_IIR_INTID_MASK; //IIR[3:0]
	
    //LedRedOn();
	/**< 字符超时     */
	if(tmp == UART_IIR_INTID_CTI){
		UART_IntReceive((LPC_UART_TypeDef*)LPC_UART1);
		if(uart1RxBuf.rx[0] == FRAME_HEAD_DATA  &&  uart1RxBuf.pIndex == 2){
			 DLL_PostMessage(IPC_MSG_UART, UART_MSG_RX1, uart1RxBuf.rx[1], 0);
		}
		
		memset(uart1RxBuf.rx, 0, uart1RxBuf.pIndex);
		uart1RxBuf.pIndex  = 0;
		
	}

	/**< FIFO数据大于触发点     */
	if(tmp == UART_IIR_INTID_RDA)
	{
		UART_IntReceive((LPC_UART_TypeDef*)LPC_UART1);
		
		if(uart1RxBuf.rx[0] == FRAME_HEAD_DATA  &&  uart1RxBuf.pIndex == 2){	
			DLL_PostMessage(IPC_MSG_UART, MSG_ID_UART1 & UINT16_MAX, uart1RxBuf.rx[1], 0);
            
            memset(uart1RxBuf.rx, 0, uart1RxBuf.pIndex);
            uart1RxBuf.pIndex  = 0;
		}
		
	}
    //LedRedOff();
    
#ifdef USE_CRITICAL_WHEN_POST 	
	OS_EXIT_CRITICAL();
#endif	    
    
}


/**	@brief 		串口2中断服务函数
  * 
  * @note			手咪按键接收
  */
void UART2_IRQHandler(void)
{
	uint32_t intsrc, tmp, tmp1;

//	printf("uart2\n");
	/* Determine the interrupt source */
	intsrc = UART_GetIntId((LPC_UART_TypeDef*)LPC_UART2);
	tmp = intsrc & UART_IIR_INTID_MASK; //IIR[3:0]
	
    if(tmp == UART_IIR_INTID_RLS){
        tmp1 = UART_GetLineStatus((LPC_UART_TypeDef *)LPC_UART2);
        tmp1 &= (UART_LSR_OE | UART_LSR_PE | UART_LSR_FE | UART_LSR_BI | UART_LSR_RXFE);
        
        if(tmp1){
//            printf("uart2 err:%d\n",__LINE__);
        }
    }
    
	/**< 字符超时     */
	if(tmp == UART_IIR_INTID_CTI){
		UART_IntReceive((LPC_UART_TypeDef*)LPC_UART2);
		
		HandKeySend(uart2RxBuf.rx);
		uart2RxBuf.pIndex  = 0;
	}

	/**< FIFO数据大于触发点     */
	if(tmp == UART_IIR_INTID_RDA)
	{
//        printf("uart2 rda:/n");
		UART_IntReceive((LPC_UART_TypeDef*)LPC_UART2);
		//UART_SendByte(LPC_UART0,0x04);
	}
}

/**	@brief 		串口3中断服务函数
  *
* 串口 3 接收FPGA数据，格式为 0xad + 163字节
  * @note
  */
void UART3_IRQHandler(void)
{
#ifdef USE_CRITICAL_WHEN_POST    
    
 #if OS_CRITICAL_METHOD == 3u	 
	 OS_CPU_SR cpu_sr  = 0u;
#endif	
	
	OS_ENTER_CRITICAL();
#endif	
    
    uint32_t intsrc, tmp, tmp1;
    static uint8_t idleCnt  = 0;
    
    static uint8_t trigger = 0;
    
    
	/* Determine the interrupt source */
	intsrc = UART_GetIntId((LPC_UART_TypeDef*)LPC_UART3);
	tmp = intsrc & UART_IIR_INTID_MASK; //IIR[3:0]
    
    
    if(tmp == UART_IIR_INTID_RLS){
        tmp1 = UART_GetLineStatus((LPC_UART_TypeDef *)LPC_UART3);
        tmp1 &= (UART_LSR_OE | UART_LSR_PE | UART_LSR_FE | UART_LSR_BI | UART_LSR_RXFE);
        
//        if(tmp1){
//            printf("uart3 err:%d\n",__LINE__);
//        }
    }
    
    
	/**< 字符超时   */
	if(tmp == UART_IIR_INTID_CTI){
		UART_IntReceive((LPC_UART_TypeDef*)LPC_UART3);
		
//        idleCnt++;
//        if(idleCnt & 0x01){
//            LedYellowOff();
//        }
//        else{
//            LedYellowOn();
//        }
        
		if(uart3RxBuf.rx[0] == FRAME_HEAD_DATA  &&  uart3RxBuf.pIndex == 164){
			memcpy( uart3Data.buf[uart3Data.curCnt], &uart3RxBuf.rx[1], 163);	
            DLL_PostMessage(IPC_MSG_UART, UART_MSG_RX3 & UINT16_MAX, 163, (uintptr_t)uart3Data.buf[uart3Data.curCnt]);			
			uart3Data.curCnt++;
			
			if(uart3Data.curCnt >= UART3_BUF_SIZE){
			  uart3Data.curCnt  = 0;
		   }
		}
		
        memset(uart3RxBuf.rx, 0, uart3RxBuf.pIndex);
		uart3RxBuf.pIndex  = 0;
	}

	/**< FIFO数据大于触发点     */
	if(tmp == UART_IIR_INTID_RDA)
	{
//        trigger++;
//        if(trigger & 0x01){
//        
//            LedRedOn();
//        }
//        else{
//            LedRedOff();
//        }
		UART_IntReceive((LPC_UART_TypeDef*)LPC_UART3);
	}
    
#ifdef USE_CRITICAL_WHEN_POST 	
	OS_EXIT_CRITICAL();
#endif	  
  
}

/*****************************串口接收数据******************************/

void UART_IntReceive(LPC_UART_TypeDef * UART_PORT)
{
	uint8_t tmpc;
	uint32_t rLen=0;
	
	while(1){
		rLen = UART_Receive(UART_PORT, &tmpc, 1, NONE_BLOCKING);
		/**< 数据有效     */		
		if(rLen){
			/**< 串口0    */
			if(UART_PORT == LPC_UART0){
				if(uart0RxBuf.pIndex<RX_MAX_SIZE){
					uart0RxBuf.rx[uart0RxBuf.pIndex] = tmpc;
					uart0RxBuf.pIndex++;
				}
			}
			/**< 串口1·     */
			else if(UART_PORT == (LPC_UART_TypeDef*)LPC_UART1){
				if(uart1RxBuf.pIndex<RX_MAX_SIZE){
					uart1RxBuf.rx[uart1RxBuf.pIndex] = tmpc;
					uart1RxBuf.pIndex++;
				}
//                else{
//                    printf("uart1 err %d\n",__LINE__);
//                }
			}
			/**< 串口2     */
			else if(UART_PORT == LPC_UART2){
				if(uart2RxBuf.pIndex<RX_MAX_SIZE){
					uart2RxBuf.rx[uart2RxBuf.pIndex] = tmpc;
					uart2RxBuf.pIndex++;
				}
                else{
//                    printf("2\n");
                }
			}
			/**< 串口3     */
			else if(UART_PORT == LPC_UART3){
				if(uart3RxBuf.pIndex<RX_MAX_SIZE){
					uart3RxBuf.rx[uart3RxBuf.pIndex] = tmpc;
					uart3RxBuf.pIndex++;
				}
//                else{
//                    printf("3");
//                }
			}

		}
		else{
			break;
		}
		
	}
	
}

/** @brief  	往缓冲区存放数据
  * 
  * @param  	UartPort	串口号 0~3
  * @param		buf	 源数据地址
	*	@param		size	数字长度
  * @return 	0成功 1失败
  * @note
  */
uint8_t PutData(LPC_UART_TypeDef* UartPort,uint8_t* buf,uint16_t size)
{
	if(UartPort == (LPC_UART_TypeDef*)LPC_UART1){
		
		if(uart1Data.curCnt<UART1_BUF_SIZE){
			memcpy(uart1Data.buf[uart1Data.curCnt],buf,size);
			uart1Data.curCnt++;
			if(uart1Data.curCnt==UART1_BUF_SIZE)
				uart1Data.curCnt = 0;
			return 1;
		}
		else{
			return 0;
		}
	}
	else if(UartPort == (LPC_UART_TypeDef*)LPC_UART3){
		if(uart3Data.curCnt<UART3_BUF_SIZE){
			memcpy(uart3Data.buf[uart3Data.curCnt],buf,size);
			uart3Data.curCnt++;
			if(uart3Data.curCnt==UART3_BUF_SIZE)
				uart3Data.curCnt = 0;
			return 1;
		}
		else{
			return 0;
		}
	}
}



/*****************************串口配置*********************************/
void Uart0_SendByte(uint8_t dat)
{

   UART_SendByte(LPC_UART0, dat);
   while (UART_CheckBusy(LPC_UART0) == SET);
}

void Uart0_SendBytes(size_t size, uint8_t* buf)
{
    while(size--){       
        UART_SendByte(LPC_UART0, *buf++);
        while (UART_CheckBusy(LPC_UART0) == SET); 
    }
}





/**	@brief 	串口2 发送数据
  * 
  * @param  	buf			发送缓冲区
	*	@param		length	数据长度
  * @note		
  */
void LCDUartSend(uint8_t *buf, uint16_t length)
{
  for(int i = 0; i < length; i++)
  {
    while (UART_CheckBusy(LPC_UART2) == SET);
    UART_SendByte(LPC_UART2, buf[i]);
  }
}



/**	@brief 		串口0初始化
  * 
  * @param  	baudRate	 波特率
  * @note
  */
void	UART0Init(uint32_t baudRate)
{

	// UART Configuration structure variable
	UART_CFG_Type UARTConfigStruct;
	// Pin configuration for UART0
	PINSEL_CFG_Type PinCfg;
	// UART FIFO configuration Struct variable
  UART_FIFO_CFG_Type UARTFIFOConfigStruct;
	
	GPDMA_Channel_CFG_Type GPDMACfg;
	
	/*
	* Initialize UART0 pin connect
	*/
	PinCfg.Funcnum = 1;
	PinCfg.OpenDrain = 0;
	PinCfg.Pinmode = 0;
	PinCfg.Pinnum = 2;				//TX
	PinCfg.Portnum = 0;
	PINSEL_ConfigPin(&PinCfg);
	PinCfg.Pinnum = 3;				//RX
	PINSEL_ConfigPin(&PinCfg);
	
	/* Initialize UART Configuration parameter structure to default state:
	* Baudrate = baudRate
	* 8 data bit
	* 1 Stop bit
	* None parity
	*/
	UART_ConfigStructInit(&UARTConfigStruct);
	UARTConfigStruct.Baud_rate = baudRate;
	UART_Init(LPC_UART0,&UARTConfigStruct);
	
	/**< DMA选配     */
#ifdef	UART0_DMA
	UARTFIFOConfigStruct.FIFO_DMAMode = ENABLE;
	Uart0DmaInit(uart0Buf,UART_BUF_SIZE);	/**< DMA 配置     */
#else
	UARTFIFOConfigStruct.FIFO_DMAMode = DISABLE;
#endif

	/**< FIFI 触发点大小选择     */
//	if(UART0_BUF_SIZE<=4)
//		UARTFIFOConfigStruct.FIFO_Level = UART_FIFO_TRGLEV0;
//	else if(UART0_BUF_SIZE<=8)
//		UARTFIFOConfigStruct.FIFO_Level = UART_FIFO_TRGLEV1;
//	else if(UART0_BUF_SIZE<=14)
//		UARTFIFOConfigStruct.FIFO_Level = UART_FIFO_TRGLEV2;
//	else
//		UARTFIFOConfigStruct.FIFO_Level = UART_FIFO_TRGLEV3;
		UARTFIFOConfigStruct.FIFO_Level = UART_FIFO_TRGLEV3;	/**< 触发点 14个字符    */
	
	
	UARTFIFOConfigStruct.FIFO_ResetRxBuf = ENABLE;
	UARTFIFOConfigStruct.FIFO_ResetTxBuf = ENABLE;
	
	// Initialize FIFO for UART0 peripheral
	UART_FIFOConfig((LPC_UART_TypeDef *)LPC_UART0, &UARTFIFOConfigStruct);
	
	//Enable UART Transmit
	UART_TxCmd(LPC_UART0, ENABLE);
	
	/* Enable UART Rx interrupt */
	UART_IntConfig((LPC_UART_TypeDef *)LPC_UART0, UART_INTCFG_RBR, ENABLE);	//接收中断
  /* Enable UART line status interrupt */
  //UART_IntConfig((LPC_UART_TypeDef *)LPC_UART0, UART_INTCFG_RLS, ENABLE);	
	
	/* preemption = 1, sub-priority = 1 */
	//NVIC_SetPriority(UART0_IRQn, ((0x01<<3)|0x01));
	NVIC_SetPriority(UART0_IRQn, NVIC_UART0);
	
	/* Enable Interrupt for UART0 channel */
	NVIC_EnableIRQ(UART0_IRQn);
	
}


/**	@brief 		串口1初始化
  * 
  * @param  	baudRate	 波特率
  * @note
  */
void	UART1Init(uint32_t baudRate)
{
	
	// UART Configuration structure variable
	UART_CFG_Type UARTConfigStruct;
	// Pin configuration for UART1
	PINSEL_CFG_Type PinCfg;
	// UART FIFO configuration Struct variable
  UART_FIFO_CFG_Type UARTFIFOConfigStruct;
	
	GPDMA_Channel_CFG_Type GPDMACfg;
	
	/*
	* Initialize UART1 pin connect
	*/
	PinCfg.Funcnum = 2;
	PinCfg.OpenDrain = 0;
	PinCfg.Pinmode = 0;
	PinCfg.Portnum = 2;
	PinCfg.Pinnum = 0;				//TX
	PINSEL_ConfigPin(&PinCfg);
	PinCfg.Pinnum = 1;				//RX
	PINSEL_ConfigPin(&PinCfg);
	
	/* Initialize UART Configuration parameter structure to default state:
	* Baudrate = baudRate
	* 8 data bit
	* 1 Stop bit
	* None parity
	*/
	UART_ConfigStructInit(&UARTConfigStruct);
	UARTConfigStruct.Baud_rate = baudRate;
	UART_Init((LPC_UART_TypeDef*)LPC_UART1,&UARTConfigStruct);
	
	/**< DMA选配     */
#ifdef	UART1_DMA
	UARTFIFOConfigStruct.FIFO_DMAMode = ENABLE;
	Uart1DmaInit(uart1Buf,UART_BUF_SIZE);	/**< DMA 配置     */
#else
	UARTFIFOConfigStruct.FIFO_DMAMode = DISABLE;
#endif

	/**< FIFI 触发点大小选择     */
	UARTFIFOConfigStruct.FIFO_Level = UART_FIFO_TRGLEV3;	/**< 触发点 14个字符    */
	
	
	UARTFIFOConfigStruct.FIFO_ResetRxBuf = ENABLE;
	UARTFIFOConfigStruct.FIFO_ResetTxBuf = ENABLE;
	
	// Initialize FIFO for UART0 peripheral
	UART_FIFOConfig((LPC_UART_TypeDef *)LPC_UART1, &UARTFIFOConfigStruct);
	
	//Enable UART Transmit
	UART_TxCmd((LPC_UART_TypeDef *)LPC_UART1, ENABLE);
	
	/* Enable UART Rx interrupt */
	UART_IntConfig((LPC_UART_TypeDef *)LPC_UART1, UART_INTCFG_RBR, ENABLE);	//接收中断
  /* Enable UART line status interrupt */
  //UART_IntConfig((LPC_UART_TypeDef *)LPC_UART1, UART_INTCFG_RLS, ENABLE);	

	
	/* preemption = 1, sub-priority = 1 */
	NVIC_SetPriority(UART1_IRQn, NVIC_UART1);
	
	/* Enable Interrupt for UART1 channel */
	NVIC_EnableIRQ(UART1_IRQn);
}


/**	@brief 		串口2初始化
  * 
  * @param  	baudRate	 波特率
  * @note
  */
void	UART2Init(uint32_t baudRate)
{
	// UART Configuration structure variable
	UART_CFG_Type UARTConfigStruct;
	// Pin configuration for UART2
	PINSEL_CFG_Type PinCfg;
	// UART FIFO configuration Struct variable
  UART_FIFO_CFG_Type UARTFIFOConfigStruct;
	
	GPDMA_Channel_CFG_Type GPDMACfg;
	
	/*
	* Initialize UART2 pin connect
	*/
	PinCfg.Funcnum = 1;
	PinCfg.OpenDrain = 0;
	PinCfg.Pinmode = 0;
	PinCfg.Portnum = 0;
	PinCfg.Pinnum = 10;				//TX
	PINSEL_ConfigPin(&PinCfg);
	PinCfg.Pinnum = 11;				//RX
	PINSEL_ConfigPin(&PinCfg);
	
	/* Initialize UART Configuration parameter structure to default state:
	* Baudrate = baudRate
	* 8 data bit
	* 1 Stop bit
	* None parity
	*/
	UART_ConfigStructInit(&UARTConfigStruct);
	UARTConfigStruct.Baud_rate = baudRate;
	UART_Init((LPC_UART_TypeDef*)LPC_UART2,&UARTConfigStruct);
	
	/**< DMA选配     */
#ifdef	UART2_DMA
	UARTFIFOConfigStruct.FIFO_DMAMode = ENABLE;
	Uart2DmaInit(uart2Buf,UART_BUF_SIZE);	/**< DMA 配置     */
#else
	UARTFIFOConfigStruct.FIFO_DMAMode = DISABLE;
#endif

	/**< FIFI 触发点大小选择     */
	UARTFIFOConfigStruct.FIFO_Level = UART_FIFO_TRGLEV3;	/**< 触发点 14个字符    */
	
	
	UARTFIFOConfigStruct.FIFO_ResetRxBuf = ENABLE;
	UARTFIFOConfigStruct.FIFO_ResetTxBuf = ENABLE;
	
	// Initialize FIFO for UART2 peripheral
	UART_FIFOConfig((LPC_UART_TypeDef *)LPC_UART2, &UARTFIFOConfigStruct);
	
	//Enable UART Transmit
	UART_TxCmd((LPC_UART_TypeDef *)LPC_UART2, ENABLE);
	
	/* Enable UART Rx interrupt */
	UART_IntConfig((LPC_UART_TypeDef *)LPC_UART2, UART_INTCFG_RBR, ENABLE);	//接收中断
  /* Enable UART line status interrupt */
  //UART_IntConfig((LPC_UART_TypeDef *)LPC_UART2, UART_INTCFG_RLS, ENABLE);	
	
	/* preemption = 1, sub-priority = 1 */
	//NVIC_SetPriority(UART2_IRQn, ((0x01<<3)|0x01));
	NVIC_SetPriority(UART2_IRQn, NVIC_UART2);
	
	/* Enable Interrupt for UART1 channel */
	NVIC_EnableIRQ(UART2_IRQn);
}


/**	@brief 		串口3初始化
  * 
  * @param  	baudRate	 波特率
  * @note
  */
void	UART3Init(uint32_t baudRate)
{
		// UART Configuration structure variable
	UART_CFG_Type UARTConfigStruct;
	// Pin configuration for UART3
	PINSEL_CFG_Type PinCfg;
	// UART FIFO configuration Struct variable
  UART_FIFO_CFG_Type UARTFIFOConfigStruct;
	
	GPDMA_Channel_CFG_Type GPDMACfg;
	
	/*
	* Initialize UART3 pin connect
	*/
	PinCfg.Funcnum = 2;
	PinCfg.OpenDrain = 0;
	PinCfg.Pinmode = 0;
	PinCfg.Portnum = 0;
	PinCfg.Pinnum = 0;				//TX
	PINSEL_ConfigPin(&PinCfg);
	PinCfg.Pinnum = 1;				//RX
	PINSEL_ConfigPin(&PinCfg);
	
	/* Initialize UART Configuration parameter structure to default state:
	* Baudrate = baudRate
	* 8 data bit
	* 1 Stop bit
	* None parity
	*/
	UART_ConfigStructInit(&UARTConfigStruct);
	UARTConfigStruct.Baud_rate = baudRate;
	UART_Init((LPC_UART_TypeDef*)LPC_UART3,&UARTConfigStruct);
	
	/**< DMA选配     */
#ifdef	UART3_DMA
	UARTFIFOConfigStruct.FIFO_DMAMode = ENABLE;
	Uart3DmaInit(uart3RxBuf.rx,UART3_DMA_SIZE);	/**< DMA 配置     */
    
	/**< FIFI 触发点大小选择     */
	UARTFIFOConfigStruct.FIFO_Level = UART_FIFO_TRGLEV0;	/**< 触发点 14个字符    */
#else
	UARTFIFOConfigStruct.FIFO_DMAMode = DISABLE;
    
	/**< FIFI 触发点大小选择     */
	UARTFIFOConfigStruct.FIFO_Level = UART_FIFO_TRGLEV3;	/**< 触发点 14个字符    */
#endif

	
	UARTFIFOConfigStruct.FIFO_ResetRxBuf = ENABLE;
	UARTFIFOConfigStruct.FIFO_ResetTxBuf = ENABLE;
	
	// Initialize FIFO for UART3 peripheral
	UART_FIFOConfig((LPC_UART_TypeDef *)LPC_UART3, &UARTFIFOConfigStruct);
	
	//Enable UART Transmit
	UART_TxCmd((LPC_UART_TypeDef *)LPC_UART3, ENABLE);
	
	/* Enable UART Rx interrupt */
	UART_IntConfig((LPC_UART_TypeDef *)LPC_UART3, UART_INTCFG_RBR, ENABLE);	//接收中断
  /* Enable UART line status interrupt */
  //UART_IntConfig((LPC_UART_TypeDef *)LPC_UART3, UART_INTCFG_RLS, ENABLE);	
	
	NVIC_SetPriority(UART3_IRQn, NVIC_UART3);
	
	/* Enable Interrupt for UART1 channel */
	NVIC_EnableIRQ(UART3_IRQn);
}


/**	@brief 		串口配置
  * 
  * @note   
  */
void UARTInit()
{
	UART0Init(115200);
	UART1Init(115200);
	UART2Init(9600);
	UART3Init(115200);
}

uint16_t GetCrc(uint8_t *p, uint16_t Length)
{
  uint16_t crc=0xffff;
	uint8_t i;
	uint16_t gx=0x1021;
	while(Length--)
	{
		for(i=0x01;i!=0;i<<=1)
		{
			if((crc&0x8000)!=0)
			{
				crc<<=1;
				crc^=gx;
			}
			else
			{
				crc<<=1;
			}
			if(((*p)&i)!=0)
			{
				crc^=gx;
			}
		}
		p++;
	}
	return ~crc;
}

void SetResultCrc(uint8_t *p, char CmdType, char Result, char ErrType)
{
  uint16_t crc = 0;
  if(Result == 'f' || Result == 'F')
  {
    p[0] = 'F';
    p[1] = CmdType;
    p[2] = ErrType;
    crc = GetCrc(p, 3);
    p[3] = crc >> 8;
    p[4] = crc & 0x00ff;
  }
  else
  {
    p[0] = Result;
    crc = GetCrc(p, 1);
    p[1] = crc >> 8;
    p[2] = crc & 0x00ff;
  }
}
/** @} */

